import os
import random
from moviepy import AudioFileClip, ImageClip, CompositeVideoClip
from utils.animation import create_animated_image_clip
from utils.subtitles import generate_srt_content
from config import config


def create_video_from_audio_image(
    audio_path: str,
    image_path: str,
    output_path: str,
    subtitle_text: str = None,
    animation_type: str = "pan",
) -> str:
    audio = None
    image = None
    final_video = None
    try:
        audio = AudioFileClip(audio_path)

        if animation_type == "random":
            animation_types = ["pan", "zoom"]
            animation_type = random.choice(animation_types)

        print(f"使用动画效果: {animation_type}")

        if animation_type == "static":
            image = ImageClip(image_path, duration=audio.duration)
            video_w, video_h = config.video.size
            video_aspect = video_w / video_h
            
            img_w, img_h = image.w, image.h
            img_aspect = img_w / img_h
            
            if img_aspect > video_aspect:
                image = image.resized(height=video_h)
            else:
                image = image.resized(width=video_w)
            
            image = image.resized((video_w, video_h))
        else:
            image = create_animated_image_clip(
                image_path, audio.duration, config.video.size, animation_type
            )

        print(f"图片加载成功，持续时间: {image.duration}秒，动画类型: {animation_type}")

        video_clips = [image]

        if subtitle_text:
            print(f"正在生成SRT字幕: {subtitle_text[:50]}...")
            
            srt_content = generate_srt_content(subtitle_text, audio.duration)
            
            srt_filename = output_path.replace(".mp4", ".srt")
            with open(srt_filename, "w", encoding="utf-8") as f:
                f.write(srt_content)
            print(f"SRT字幕文件已保存: {srt_filename}")

        final_video = CompositeVideoClip(video_clips, size=config.video.size)
        final_video = final_video.with_audio(audio)

        final_video.write_videofile(
            output_path, fps=config.video.segment_fps, audio_codec="aac", codec="libx264"
        )

        return output_path

    except Exception as e:
        print(f"视频合成错误: {e}")
        raise
    finally:
        try:
            if audio is not None:
                audio.close()
        except Exception:
            pass
        try:
            if image is not None:
                image.close()
        except Exception:
            pass
        try:
            if final_video is not None:
                final_video.close()
        except Exception:
            pass


def embed_srt_to_video(input_video_path: str, srt_path: str, output_video_path: str) -> str:
    """
    使用ffmpeg将SRT软字幕内嵌到MP4视频中（作为软字幕轨道，而非烧录）。

    Args:
        input_video_path: 源视频路径
        srt_path: SRT字幕文件路径
        output_video_path: 输出视频路径

    Returns:
        输出视频文件路径
    """
    try:
        # 说明：moviepy不直接处理软字幕轨道，这里调用系统ffmpeg。
        # 软字幕保留原视频轨与音轨，不进行重编码，提升速度与画质保持。
        # 对于mp4容器，常用mov_text编码器承载字幕。
        # -c copy 避免重编码视频/音频，但字幕需要指定编码器。
        import subprocess

        cmd = [
            "ffmpeg",
            "-y",
            "-i", input_video_path,
            "-i", srt_path,
            # 保留原视频与音频，不重编码
            "-c:v", "copy",
            "-c:a", "copy",
            # 将SRT转为MP4可用的mov_text字幕
            "-c:s", "mov_text",
            # 明确映射：视频/音频来自第一个输入，字幕来自第二个输入
            "-map", "0:v:0",
            "-map", "0:a?",
            "-map", "1:0",
            # 设置字幕语言与默认轨道
            "-metadata:s:s:0", "language=chi",
            "-metadata:s:s:0", "title=Chinese",
            "-disposition:s:0", "default",
            "-movflags", "+faststart",
            output_video_path,
        ]
        print("正在内嵌SRT字幕到视频...", " ".join(cmd))
        subprocess.run(cmd, check=True)
        print(f"字幕已内嵌完成: {output_video_path}")
        return output_video_path
    except Exception as e:
        print(f"字幕内嵌失败: {e}")
        raise


def burn_srt_to_video(input_video_path: str, srt_path: str, output_video_path: str) -> str:
    """
    使用ffmpeg滤镜将SRT硬字幕（烧录）到视频画面中。

    注意：该过程会重编码视频轨，以保证字幕渲染进画面。

    Args:
        input_video_path: 源视频路径
        srt_path: SRT字幕文件路径
        output_video_path: 输出视频路径

    Returns:
        输出视频文件路径
    """
    try:
        import subprocess
        # 通过libass的force_style控制字体大小/描边/边距
        style_parts = [
            f"Fontsize={config.subtitle.font_size}",
            f"Outline={config.subtitle.stroke_width}",
            f"MarginV={config.subtitle.margin_bottom}",
            f"MarginL={config.subtitle.margin_horizontal}",
            f"MarginR={config.subtitle.margin_horizontal}",
            # 尝试指定常见中文字体，若系统无该字体则libass会回退
            "FontName=PingFang SC",
            "BorderStyle=1"
        ]
        force_style = ",".join(style_parts)
        # 注意：-vf 参数为单一字符串，使用ffmpeg滤镜自身的引号处理路径空格
        vf_arg = f"subtitles='{srt_path}':force_style='{force_style}'"

        cmd = [
            "ffmpeg", "-y",
            "-i", input_video_path,
            "-vf", vf_arg,
            "-c:v", "libx264",
            "-preset", "medium",
            "-crf", "18",
            "-c:a", "copy",
            "-movflags", "+faststart",
            output_video_path,
        ]
        print("正在烧录SRT字幕到视频...", " ".join(cmd))
        subprocess.run(cmd, check=True)
        print(f"硬字幕已生成: {output_video_path}")
        return output_video_path
    except Exception as e:
        print(f"硬字幕烧录失败: {e}")
        raise